<template>
  <div v-loading="loading" class="employees-container">
    <PageTools>
      <template #left>
        <span>本月：公积金提交日期有变更</span>
      </template>
      <template #right>
        <el-button size="mini" type="primary" @click.native="$router.push('/update')">导入</el-button>
        <el-button size="mini" type="primary" @click="handleExport">导出</el-button>
        <el-button size="mini" type="primary" icon="el-icon-plus" @click.native="addThis">新增员工</el-button>
      </template>
    </PageTools>
    <!-- 员工列表 -->
    <el-card style="margin-top: 10px;">
      <!-- el-table里面 :data动态导入储存数据的数组 -->
      <el-table border :data="list">
        <!-- el-table-column type设置序号 prop导入数组里面的单独数据 -->
        <el-table-column label="序号" type="index" sortable="" />
        <el-table-column label="头像" prop="staffPhoto">
          <template v-slot="scope">
            <!-- 设置饿了么ui提供的图片显示组件 -->
            <!-- :src是动态绑定图片的url地址 -->
            <el-image class="staff" :src="scope.row.staffPhoto" @click="previewImg(scope.row.staffPhoto)">
              <!-- 调用饿了么ui提供的 图片加载失败具名插槽 如果图片加载失败 显示默认的图片 -->
              <div slot="error">
                <img class="staff" :src="defaultImage">
              </div>
            </el-image>
          </template>
        </el-table-column>
        <el-table-column label="姓名" prop="username" sortable="" />
        <el-table-column label="工号" prop="workNumber" sortable="" />
        <el-table-column label="聘用形式" prop="formOfEmployment" sortable="">
          <!-- 调用作用域插槽(饿了么组件提供的插槽 ) 把服务器获取的数字类型数据 格式化为文字(状态是1 让其变为正式) -->
          <template v-slot="scope">
            <!-- 设置方法 需要导入列表格式化数据 格式化作用域插槽的内容 -->
            {{ formatHireTyp(scope.row.formOfEmployment) }}
          </template>
        </el-table-column>
        <el-table-column label="部门" prop="departmentName" sortable="" />
        <!-- 入职时间需要导入 时间格式化插件 -->
        <el-table-column label="入职时间" prop="timeOfEntry" sortable="">
          <!-- 设置作用域插槽格式化时间信息 -->
          <template slot-scope="scope">
            <!-- 调用全局的时间格式化组件 -->
            {{ scope.row.timeOfEntry|formatTime }}
          </template>
        </el-table-column>
        <el-table-column label="账户状态" prop="enableState" sortable="">
          <template slot-scope="scope">
            <el-switch :value="Boolean(scope.row.enableState)" active-color="#13ce66" inactive-color="#ff4949" />
          </template>
        </el-table-column>
        <el-table-column label="操作" sortable="" fixed="right" width="280">
          <!-- 作用域插槽 绑定饿了么ui提供的 获取数据方法 -->
          <template v-slot="scope">
            <!-- 设置动态路由 跳转到个人信息 -->
            <el-button type="text" size="small" @click.native="$router.push('/employees/detail/'+scope.row.id)">查看</el-button>
            <el-button type="text" size="small">转正</el-button>
            <el-button type="text" size="small">调岗</el-button>
            <el-button type="text" size="small">离职</el-button>
            <!-- 携带角色id 传给权限管理组件 -->
            <el-button type="text" size="small" @click="assignRole(scope.row.id)">角色</el-button>
            <el-button type="text" size="small" @click.native="handleDelete(scope.row.id)">删除</el-button>
          </template>
        </el-table-column>
      </el-table>
      <!-- 分页组件 -->
      <div style="height: 60px; margin-top: 10px">
        <!-- 设置分页 -->
        <el-pagination background :current-page="filterParams.page" :page-size="filterParams.size" layout="prev, pager, next, jumper, slot,->, total" @current-change="handleCurrentChange" />
      </div>
    </el-card>
    <!-- 添加员工组件 -->
    <addUser :show-dialog.sync="showDialog" />
    <!-- 二维码弹窗组件-->
    <el-dialog title="二维码" :visible.sync="showCodeDialog">
      <el-row type="flex" justify="center">
        <!-- canvas画布用于绘制二维码 -->
        <canvas ref="myCanvas" />
      </el-row>
    </el-dialog>
    <!-- 权限分配弹窗 携带用户id值 和显示隐藏传给权限管理组件 -->
    <assign-role :user-id="userId" :show-role-dialog.sync="showRoleDialog" />
  </div>
</template>
<script>
// 导入权限分类弹窗
import AssignRole from './components/assign-role.vue'
// 导入增删改查的api接口
import { reqGetEmployeeList, reqDelEmployee } from '../../api/employees'
// 导入添加用户的子组件
import addUser from './components/AddEmployee.vue'
// 导入员工列表数据格式化
import Types from '@/api/constant/employees.js'
// 导入时间格式化插件
import moment from 'moment'
// 导入二维码生成器
import QrCode from 'qrcode'
export default {
  name: 'Employees',
  components: {
    addUser,
    AssignRole
  },
  data () {
    return {
      // 分配角色的用户id
      userId: '',
      // 设置权限管理弹窗
      showRoleDialog: false,
      // 二维码弹窗组件状态位
      showCodeDialog: false,
      // 设置如果图片加载失败 显示默认图片
      defaultImage: 'https://dss0.bdstatic.com/70cFuHSh_Q1YnxGkpoWK1HF6hhy/it/u=2146034403,1504718527&fm=26&gp=0.jpg',
      // 设置添加员工弹窗的状态位
      showDialog: false,
      // 设置加载状态位
      loading: false,
      // 通过页码实现分页效果的参数
      filterParams: {
        // 页码
        page: 1,
        // 每页的条数
        size: 10
      },
      // 员工总条数(默认是0)
      total: 0,
      // 储存获取到的员工列表
      list: []
    }
  },
  created () {
    this.loadEmployeeList()
  },
  methods: {
    // 设置添加权限
    addThis () {
      // 判断是否拥有权限
      if (this.$isOk('POINT-USER-ADD')) { // POINT-USER-ADD是按钮权限的内容 需要传给$isOk 进行判断
        // 如果有 显示弹窗
        this.showDialog = true
      }
    },
    // ~ 设置添加窗口的权限
    assignRole (id) {
      // ~ 判断是否拥有权限

      this.userId = id
    },
    // 二维码窗口设置
    previewImg (url) {
      // 显示弹窗
      this.showCodeDialog = true
      // 把url转换为二维码并绘制到canvas画布中
      // 注意：这里是无法直接获取this.$refs.myCanvas元素的
      this.$nextTick(() => {
        // 保证弹窗已经完成渲染，此时才可以获取里面的DOM元素
        QrCode.toCanvas(this.$refs.myCanvas, url)
      })
    },
    // 把后端传来的json数据 进行转换(二维数组格式)
    jsonToArray (headers, jsonData) {
      // 获取对象所有的属性名object.keys(设置为标题)
      // 获取员工Excel的标题数据(插件的标题)
      // header = ["姓名", "手机号", "入职日期", "聘用形式", "转正日期", "工号", "部门"]
      const header = Object.keys(headers)
      // 把转换好的数据 存在该数组中
      const results = []
      // 动态转换服务器获取的数据
      // 遍历获取服务器中的所有数据(遍历服务器返回的所有数据)
      jsonData.forEach(item => { // item参数 是服务器所有的数据
        // 储存一行的数据
        const row = []
        // 遍历获取到服务器数据中的每一条(遍历服务器返回所有数据中的每一条)
        header.forEach(title => { // title参数 是服务器每一条的数据
          // 根据title获取的对应的数据(获取属性名)
          // 根据title的中文信息获取对应的英文信息(转换服务器传来的数据)
          const attrName = headers[title]// username
          console.log(headers.title)
          // 根据英文属性名称获取相应的值(获取属性值)
          let attrValue = item[attrName] // 王果果
          console.log(attrName)
          // ~ 判断时间相关信息(转换时间格式)
          if (['timeOfEntry', 'correctionTime'].includes(attrName)) {
            // 判断 如果是时间名称的属性名 如果是时间名称 进行格式化
            // 如果时间有问题 不做处理(时间是空的话)
            try {
              // 导入时间格式化插件 格式化时间
              attrValue = moment(attrValue).format('yyyy-MM-DD')
            } catch (error) {
              console.log(error)
            }
          }
          // ~ 判断聘用形式
          if (attrName === 'formOfEmployment') {
            // 查找符合条件的聘用形式
            const info = Types.hireType.find(item => {
              // 进行比对
              return item.id === attrValue
            })
            // 把找到的形式 改成文本(进行效验 如果没有聘用形式 那就赋给原值)
            attrValue = info ? info.value : attrValue
          }
          // 把对应的值 放入第二位数组
          row.push(attrValue)
        })
        // 生成一个替换好的员工输入
        results.push(row)
      })
      // 返回遍历后的所有数据
      return results
    },
    // 获取需要导出的数据(格式化后端传来的数据)
    async getExportData (headers) { // 参数接收设置的转换格式
      try {
        // 根据分页来获取数据(分页设置为 size需要设置为总条数)
        const ret = await reqGetEmployeeList({
          // 加载的数据为一页
          page: 1,
          // 加载的总条数为服务器返回的总条数
          size: this.total
        })
        // 异常处理
        if (ret.code === 10000) {
          // 如果获取成功 获取导出的数据(需要传给转换方法 把获取的json数据进行转换)
          // 携带转换格式 和 服务器数据 创给jsonToArray 进行转换
          return this.jsonToArray(headers, ret.data.rows)
        } else {
          // 如果不成功 返回一个空数组
          return []
        }
      } catch {
        // 如果不成功 返回一个空数组
        return []
      }
    },
    // 导出Excel表格
    handleExport () {
      // 需要设置转换的格式(转换服务器传来的数据)
      const headers = {
        '姓名': 'username',
        '手机号': 'mobile',
        '入职日期': 'timeOfEntry',
        '聘用形式': 'formOfEmployment',
        '转正日期': 'correctionTime',
        '工号': 'workNumber',
        '部门': 'departmentName'
      }
      // 实现导出Excel功能 这里用到了懒加载(用到的时候加载)
      import('@/vendor/Export2Excel').then(async excel => {
        // 获取员工列表数据（已经是二维数组 格式化后的数据）
        const list = await this.getExportData(headers) // 传入转换服务器数据的格式
        excel.export_json_to_excel({
          header: Object.keys(headers), // 表头 必填 提取转换后数据的名称
          data: list, // 具体数据 必填(把服务器格式化的数据 传入到这里)
          filename: 'excel-list', // 非必填,导出的文件名称
          autoWidth: true, // 非必填，控制内容自适应宽度
          bookType: 'xlsx' // 非必填，导出的文件后缀
        })
      })
    },
    // 格式化 作用域插槽里的数据
    formatHireTyp (type) { // 接收作用域插槽传来的数据
      // 使用find方法 查询符合格式化的数据
      const obj = Types.hireType.find(item => { // 导入格式化规则
        return item.id === type // 格式化条件 查询 作用域插槽传来的数据
      })
      // 把查完的结果 return获取 赋值给作用域插槽
      // 进行判断 如果查询到存在筛选内容 那就赋值给其正式的数据 如果没查到 返回原数据
      return obj ? obj.value : type
    },
    // 通过页码方式 获取员工的数据
    async loadEmployeeList () {
      this.loading = true
      try {
        // 获取员工的数据
        const ret = await reqGetEmployeeList(this.filterParams)
        // 判断是否获成功
        if (ret.code === 10000) {
          // 储存 员工总条数
          this.total = ret.data.total
          // 把获取到的员工数据储存
          this.list = ret.data.rows
          this.loading = false
        } else { // 非网络问题获取失败提示用户
          this.$message.error('获取数据失败')
          this.loading = false
        }
      } catch (error) { // 网络问题获取失败 提示用户
        this.$message.error('获取数据失败')
        this.loading = false
      }
    },
    // 点击相应页码 获取相应的页码数据
    async handleCurrentChange (index) { // 接收template模板传来的 当前页码数值
      // 点击后 把存在数据中的页码 赋值给当前页码
      this.filterParams.page = index
      // 赋值后重新调用接口 获取当前页码的数据
      this.loadEmployeeList()
    },
    // 设置删除功能
    handleDelete (id) {
      // 删除前进行提示
      this.$confirm('确认要删除角色吗？, 是否继续?', '提示', {
        confirmButtonText: '确定',
        cancelButtonText: '取消',
        type: 'warning'
      }).then(async () => {
        const ret = await reqDelEmployee(id)
        if (ret.code === 10000) {
          // 删除成功 刷新页面
          this.loadRoleList()
        } else {
          // 删除失败 提示用户
          this.$message.error(ret.message)
        }
      }).catch((err) => {
        if (err !== 'cancel') { // 需要排除 取消按钮进入catch行为(点击取消会进入catch 需要判断 排除这个删除失败)
          // 删除角色失败(网络问题)
          this.$message.error('删除角色失败')
        }
      })
    }
  }
}
</script>
<style lang="scss">
.employees-container .el-table--enable-row-transition .el-table__body td {
  -webkit-transition: background-color 0.25s ease;
  transition: background-color 0.25s ease;
  text-align: center;
}
.employees-container {
  .staff {
    width: 70px;
    height: 70px;
    border-radius: 50%;
  }
}
.el-image__inner {
  vertical-align: top;
  cursor: pointer;
}
</style>
